package com.cskaoyan.javase.oop2.encapsulate._1extends._9override._1grammar;

/**
 * 方法覆盖的语法
 * 方法覆盖不单单是父子类中出现了同名成员方法,它有固定语法和使用形式
 *
 * 方法覆盖针对于以下一个成员方法:
 * [访问权限修饰符] 返回值类型 方法名(形参列表){
 *     // 方法体
 * }
 * 先学习一个注解:@Override
 * 该注解放在子类重写父类方法的方法头上面,用来检测该方法是否重写自父类
 * 如果没有报错,则说明是重写方法,否则不是重写方法
 *
 * 假如在子类中要重写父类如上的一个成员方法,其语法限制是:
 *      1.访问权限修饰符会对方法重写造成影响吗?
 *          子类可以重写父类方法的访问权限修饰符
 *          但只能重写的更宽容,不能更严格,当然保持一致也是允许的
 *          从严格到宽松:
 *          private --> 默认 --> protected --> public
 *
 *      2.子类能不能重写父类方法的返回值类型呢?
 *          实际上不需要完全保持一致,但也不是乱重写的
 *          子类重写方法的返回值类型,必须和父类方法保持"兼容"
 *          何为兼容呢?
 *          自行测试一下
 *          提示: 考虑基本数据类型和引用数据类型返回值类型
 *
 *      3.父子类重写方法的方法名必须严格保持一致
 *      4.父子类重写方法的形参列表也必须严格保持一致
 *          注意: 形参的名字不影响方法调用,所以形参的名字不需要保持一致
 *          其它的,比如数据类型,顺序等是需要严格保持一致的
 *      5.方法体没有任何要求,子类方法重写可以随便写方法体.
 *
 * 结合方法的重写,再来描述一次"对象名.成员方法"的调用机制:
 *      首先引用决定了能够调用方法的范围
 *      其次方法的执行结果一定要根据对象的具体类型来决定:
 *          如果在执行一个方法时,对象的类型中已经重写了该方法
 *          那么执行的结果,一定是子类中重写的方法执行结果
 *
 * Overload vs Override
 * 相同点:
 *      1.无论是重载还是重写,它们都要求两个方法同名
 *      2.它们都不限制方法体
 * 不同点:
 *      1.重载是发生在一个类当中的,而重写必然发生在两个类之间.
 *      2.访问权限修饰符,方法的重载不关心
 *          但是子类重写父类方法,权限只能更宽松,不能更严格,可以保持一致
 *      3.返回值类型,方法的重载不关心
 *          但是子类重写父类方法,要保持返回值类型上的"兼容"
 *      4.形参列表:
 *          方法的重载要求形参列表必须不同
 *          方法的重写要求必须相同
 *          (注: 形参的名字不影响,无所谓)
 *
 * @since 16:22
 * @author wuguidong@cskaoyan.onaliyun.com
 */
public class Demo {
}

class Father {
    protected void test(int a) {
    }
}

class Son extends Father {
    @Override
    public void test(int b) {
    }
}